package com.bigdata.assignment.problem2;

import org.apache.hadoop.io.IntWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Partitioner;

/**
 * AlphabetPartitioner
 * 按单词首字母进行分区规则：
 *  A-F -> partition 0
 *  G-N -> partition 1
 *  O-S -> partition 2
 *  T-Z -> partition 3
 *
 *  字符处理规则：
 *  - 首字母统一转为大写来判定
 *  - 数字开头 (0-9) -> partition 0
 *  - 非字母非数字（特殊字符） -> partition 0
 *  - 空字符串或 null -> partition 0
 *
 *  为兼容任意 numPartitions，返回计算出的分区号 % numPartitions
 */
public class AlphabetPartitioner extends Partitioner<Text, IntWritable> {

    @Override
    public int getPartition(Text key, IntWritable value, int numPartitions) {
        if (numPartitions == 0) return 0;

        if (key == null) return 0;

        String s = key.toString();
        if (s.isEmpty()) return 0;

        char c = s.charAt(0);
        // 转为大写（考虑 Unicode，但这里只取基本拉丁字母）
        char up = Character.toUpperCase(c);

        int partition;
        if (up >= 'A' && up <= 'F') {
            partition = 0;
        } else if (up >= 'G' && up <= 'N') {
            partition = 1;
        } else if (up >= 'O' && up <= 'S') {
            partition = 2;
        } else if (up >= 'T' && up <= 'Z') {
            partition = 3;
        } else if (Character.isDigit(c)) {
            partition = 0;
        } else {
            // 其他 Unicode 字符（例如中文、符号）视作特殊字符，落到 partition 0
            partition = 0;
        }

        // 防止 numPartitions != 4 的情况，做模运算保证合法
        return partition % numPartitions;
    }
}
